package ai.chat2db.server.web.start.config.oauth.impl;

import ai.chat2db.server.domain.api.enums.RoleCodeEnum;
import ai.chat2db.server.domain.api.enums.ValidStatusEnum;
import ai.chat2db.server.domain.api.model.User;
import ai.chat2db.server.domain.api.service.UserService;
import ai.chat2db.server.domain.core.cache.CacheKey;
import ai.chat2db.server.domain.core.cache.MemoryCacheManage;
import ai.chat2db.server.domain.repository.enums.LoginTypeEnum;
import ai.chat2db.server.tools.base.excption.BusinessException;
import ai.chat2db.server.tools.common.config.Chat2dbProperties;
import ai.chat2db.server.tools.common.enums.ModeEnum;
import ai.chat2db.server.tools.common.model.LoginUser;
import ai.chat2db.server.tools.common.util.ContextUtils;
import ai.chat2db.server.web.start.config.oauth.OauthService;
import ai.chat2db.server.web.start.controller.oauth.request.LoginRequest;
import cn.dev33.satoken.stp.StpInterface;
import cn.dev33.satoken.stp.StpUtil;
import jakarta.annotation.Resource;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;

import java.util.List;

/**
 * @author Asu
 * @version 1.0
 * @date 2024/5/20 10:59
 * @desc 本地验证service
 */
@Service
public class NativeOauthService implements OauthService, StpInterface {

    @Resource
    private UserService userService;

    @Resource
    private Chat2dbProperties chat2dbProperties;

    @Override
    public String oauthType() {
        return "NATIVE";
    }

    @Override
    public User login(LoginRequest loginRequest) {
        User user = userService.query(loginRequest.getUserName(), loginRequest.getLoginType()).getData();
        // 校验用户是否存在
        this.validateUser(user);
        String loginType = loginRequest.getLoginType();
        if (LoginTypeEnum.NATIVE.getLoginType().equals(loginType)) {
            // 对比密码
            if (!user.getPassword().equals(loginRequest.getPassword())) {
                throw new BusinessException("oauth.passwordIncorrect");
            }
        }
        return user;
    }

    @Override
    public LoginUser getLoginUser(String userId) {

        Long uid;
        // Not logged in
        if (!StringUtils.isNumeric(userId)) {
            if (chat2dbProperties.getMode() == ModeEnum.DESKTOP) {
                uid = RoleCodeEnum.DESKTOP.getDefaultUserId();
            } else {
                return null;
            }
        } else {
            uid = Long.parseLong(userId);
        }
        return MemoryCacheManage.computeIfAbsent(CacheKey.getLoginUserKey(uid), () -> {
            User user = userService.query(uid).getData();
            if (user == null) {
                return null;
            }
            if (!ValidStatusEnum.VALID.getCode().equals(user.getStatus())) {
                StpUtil.logout();
                throw new BusinessException("oauth.invalidUserName");
            }
            boolean admin = RoleCodeEnum.ADMIN.getCode().equals(user.getRoleCode());

            return LoginUser.builder()
                    .id(user.getId())
                    .nickName(user.getUserName())
                    .admin(admin)
                    .roleCode(user.getRoleCode())
                    .build();
        });
    }

    @Override
    public List<String> getPermissionList() {
        return getPermissionList(ContextUtils.getUserId(), null);
    }

    @Override
    public List<String> getRoleList() {
        return getRoleList(ContextUtils.getUserId(), null);
    }

    @Override
    public List<String> getPermissionList(Object o, String s) {

        return List.of("ADMIN");
    }

    @Override
    public List<String> getRoleList(Object o, String s) {
        return List.of("ADMIN");
    }
}
